/*
 * Copyright 2017-2020 Wuwei Tengyu Logistics Center Co., Ltd.
 */

package com.goblin.common.util;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * desc: .
 *
 * @author go blin
 * <p>
 * 2019/11/7 10:04
 */
public final class TransforEntity {

    /**
     * desc: T类型属性 copy到 D类型， 返回 D类型
     *
     * @param <D> not empty
     * @param <T> not empty
     * @author go blin
     * <p>
     * 2019/6/13 15:45
     */
    public static <T, D> D copy(Class<T> _classT, Class<D> _classD, Object po) {
        D poD = null;
        try {
            poD = _classD.newInstance();
        } catch (InstantiationException ex) {
        } catch (IllegalAccessException ex) {
        }
        Method[] methods = _classT.getDeclaredMethods();
        for (Method method : methods) {
            String methodName = method.getName();
            if (methodName.matches("get(.*)")) {
                try {
                    Object paramD = method.invoke(po);
                    Class _class = paramD.getClass();
                    String setMethod = methodName.replace("get", "set");
                    Method methodD = null;
                    if (Timestamp.class.equals(paramD.getClass())) {
                        try {
                            _classD.getDeclaredMethod(setMethod, paramD.getClass());
                        } catch (NoSuchMethodException ex) {
                            _class = Date.class;
                        }
                    }
                    methodD = _classD.getDeclaredMethod(setMethod, _class);
                    methodD.invoke(poD, paramD);

                } catch (IllegalAccessException ex) {
                } catch (InvocationTargetException ex) {
                } catch (NoSuchMethodException ex) {
                } catch (Exception ex) {
                }
            }
        }
        return poD;
    }

    /**
     * desc: copy dest Object not null properties to source Object.
     *
     * @param <T> copy class
     * @return dest
     * @author go blin
     * <p>
     * 2019/6/13 15:45
     */
    public static <T> T copyPropertiesNotNull(Class<T> _class, T dest, T source) {

        Method[] methods = _class.getDeclaredMethods();
        for (Method method : methods) {
            String methodName = method.getName();
            if (methodName.matches("get(.*)")) {
                try {
                    Object paramD = method.invoke(source);
                    if (paramD != null) {
                        String setMethod = methodName.replace("get", "set");
                        Class _tmp = paramD.getClass();
                        if (paramD.getClass().equals(ArrayList.class)) {
                            _tmp = List.class;
                        }
                        Method methodD = _class
                                .getDeclaredMethod(setMethod, _tmp);
                        methodD.invoke(dest, paramD);
                    }
                } catch (IllegalAccessException ex) {
                } catch (InvocationTargetException ex) {
                } catch (NoSuchMethodException ex) {
                } catch (Exception ex) {
                }
            }
        }
        return dest;
    }
}
